﻿using System;
using MongoDB.Driver;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Sustainalytics.Entities.ProductInvolvement;

namespace Sustainalytics.DataLayer.PI.Tests
{
    [TestClass()]
    public class InputFileRepositoryTests
    {

        private string _dbCnx;
        private string _databaseName;
        private string _collectionName;
        private  MongoDatabase _database = null;

        public InputFileRepositoryTests()
        {
            _dbCnx = "mongodb://localhost:27017/ClientPlatform_Tests";
            _databaseName = "ClientPlatform_Tests";
            _collectionName = typeof(PIInputFile).Name;

            var mongoClient = new MongoClient(_dbCnx);
            var server = mongoClient.GetServer();
            _database = server.GetDatabase(_databaseName);
        }

        [TestMethod()]
        public void CreateTest()
        {
            var newobj = new PIInputFile() { Id = Guid.NewGuid(), Name = "test" };
            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");     
            rep.Create(newobj);
            var foundObj = _database.GetCollection<PIInputFile>(_collectionName).FindOneById(newobj.Id);
            Assert.AreEqual(newobj.Id, foundObj.Id, "create PIInputFile fails");
            Assert.AreEqual(newobj.Name, foundObj.Name, "create PIInputFile fails");

        }


        [TestMethod()]
        public void Update1Test()
        {
            var newobj = new PIInputFile() { Id = Guid.NewGuid(), Name = "test" };
            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");

            rep.Create(newobj);
            newobj.Name = "updated";
            rep.Update(newobj.Id, newobj);

            var foundObj = _database.GetCollection<PIInputFile>(_collectionName).FindOneById(newobj.Id);
            Assert.AreEqual(newobj.Id, foundObj.Id, "create  PIInputFile fails");
            Assert.AreEqual(newobj.Name, foundObj.Name, "update PIInputFile fails");

        }

        [TestMethod()]
        public void Update2Test()
        {
            var newobj = new PIInputFile() { Id = Guid.NewGuid(), Name = "test" };
            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");

            rep.Create(newobj);
            newobj.Name = "updated";
            rep.Update(newobj);

            var foundObj = _database.GetCollection<PIInputFile>(_collectionName).FindOneById(newobj.Id);
            Assert.AreEqual(newobj.Id, foundObj.Id, "create  PIInputFile fails");
            Assert.AreEqual(newobj.Name, foundObj.Name, "update PIInputFile fails");

        }

        [TestMethod()]
        public void DeleteTest()
        {
            var newobj = new PIInputFile() { Id = Guid.NewGuid(), Name = "test" };
            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");

            rep.Create(newobj);
            
            var foundObj = _database.GetCollection<PIInputFile>(_collectionName).FindOneById(newobj.Id);
            Assert.AreEqual(newobj.Id, foundObj.Id, "create PIInputFile fails");
            Assert.AreEqual(newobj.Name, foundObj.Name, "create PIInputFile fails");


            rep.Delete(newobj.Id);
            var removedObj = _database.GetCollection<PIInputFile>(_collectionName).FindOneById(newobj.Id);
            Assert.AreEqual(null, removedObj, "delete  PIInputFile fails");
        }


        [TestMethod()]
        public void ReadTest()
        {
            var newobj = new PIInputFile() { Id = Guid.NewGuid(), Name = "test" };
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj);

            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");
            var foundObj =  rep.Read(newobj.Id);             
            Assert.AreEqual(newobj.Id, foundObj.Id, "create PIInputFile fails");
            Assert.AreEqual(newobj.Name, foundObj.Name, "create PIInputFile fails");

        }


        [TestMethod()]
        public void ReadAllTest()
        {
            _database.GetCollection<PIInputFile>(_collectionName).RemoveAll();
            var newobj1 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test1" };
            var newobj2 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test2" };
            var newobj3 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test3" };
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj1);
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj2);
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj3);

            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");
            
            var foundObjs = rep.ReadAll();



            Assert.AreEqual(foundObjs.Count, 3, "read all  PIInputFile fails");
            Assert.AreEqual(foundObjs[2].Name, "test3", "create PIInputFile fails");

        }

        [TestMethod()]
        public void ReadLatestTest()
        {
            _database.GetCollection<PIInputFile>(_collectionName).RemoveAll();
            var newobj1 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test1" };
            var newobj2 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test2" };
            var newobj3 = new PIInputFile() { Id = Guid.NewGuid(), Name = "test3" };


            newobj1.History.Add(new PIInputHistory() { DateTime = DateTime.Now, Details = "1", Status = PIUploadStatus.UploadValid});
            newobj2.History.Add(new PIInputHistory() { DateTime = DateTime.Now.AddMinutes(5), Details = "2", Status = PIUploadStatus.UploadValid });
            newobj3.History.Add(new PIInputHistory() { DateTime = DateTime.Now.AddMinutes(7), Details = "3", Status = PIUploadStatus.UploadValid });
            newobj3.History.Add(new PIInputHistory() { DateTime = DateTime.Now.AddMinutes(15), Details = "3", Status = PIUploadStatus.UploadValid });

            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj1);
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj2);
            _database.GetCollection<PIInputFile>(_collectionName).Insert(newobj3);
            System.Threading.Thread.Sleep(1000);
            var rep = new InputFileRepository("mongodb://localhost:27017/ClientPlatform_Tests");
            var foundObj = rep.ReadLatest();

            Assert.AreEqual(foundObj.Name, "test3", "read latest  PIInputFile fails");            

        }

    }
}
